// Copyright 2019 The rhyme_lph Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
// G [author] rhyme_lph
// z [email]  rhymelph@gmail.com
// s [github] https://github.com/rhymelph

import 'package:base_plugin/base_plugin.dart';
import 'package:dio/src/response.dart';
import 'package:finance_app/src/entities/product_entity.dart';
import 'package:finance_app/src/http_service/http_product_service.dart';
import 'package:finance_app/src/mixin/filter_product_service_sort_mixin.dart';
import 'package:finance_app/src/mixin/format_group_map_mixin.dart';
import 'package:finance_app/src/mixin/refresh_mixin.dart';
import 'package:finance_app/src/mixin/search_data_list_mixin.dart';
import 'package:finance_app/src/router_gen/router_gen_providers.dart';
import 'package:flutter/material.dart';
import 'package:finance_app/src/page/dashboard/products_services/linked_products_page.dart';

class LinkedProductsProvider extends BaseProvider<List<ProductEntity>>
    with
        SearchDataListMixin,
        RefreshMixin<List<ProductEntity>, List<ProductEntity>>,
        FormatGroupMapLocalMixin<ProductEntity> {
  List<ProductEntity> currentSelects = [];

  @override
  Future get dataFuture =>
      HttpProductService.productList(currentSelects.length > 0 ? 0 : 1);

  @override
  List<ProductEntity> get dataList => data;

  @override
  Future get refreshFuture => dataFuture;

  @override
  void searchRefreshData(searchData) {
    transformData(data, false);
    update();
  }

  @override
  List<ProductEntity> getFromRequestResult(
      Response<dynamic> result, bool isRefresh) {
    if (isRefresh) {
      groupMap.clear();
    }
    List<ProductEntity> data = getEntityFromResult<List<ProductEntity>>(result);
    transformData(data, false);
    return data;
  }

  @override
  FutureOr<List<ProductEntity>> transformData(
      List<ProductEntity> d, bool isCache) {
    groupMap.clear();
    contactToMap(d);
    return super.transformData(d, isCache);
  }

  void contactToMap(List<ProductEntity> list) {
    sortGroupToMap(list,
        sort: (a, b) => sortName(a, b, (t) => t.name),
        group: (a) => groupFirstName(a, (t) => t.name),
        filter: (a) => onFilterSearch(searchController.text, a.name));
  }

  void onShowAddProductName(String text) async {
    searchFocusNode.unfocus();
    final result =
        await Routes.navigateTo(RouterGenProviders.newProductPage, params: {
      'text': text,
      'isPro': true,
    });
    if (result != null) {
      data.add(result);
      transformData(data, false);
      onSelectProduct(result);
    }
  }

  void onShowAddProduct() async {
    searchFocusNode.unfocus();
    final result =
        await Routes.navigateTo(RouterGenProviders.newProductPage, params: {
      'isPro': true,
    });
    if (result != null) {
      data.add(result);
      transformData(data, false);
      onSelectProduct(result);
    }
  }

  void onSelectProduct(ProductEntity value) async {
    final finder = currentSelects
        .firstWhere((element) => element.id == value.id, orElse: () => null);
    if (finder != null) {
      currentSelects.removeWhere(
        (element) => element.id == value.id,
      );
    } else {
      currentSelects.add(value);
    }
    update();
  }

  void onSave() {
    obtainContext?.call((context) {
      Navigator.of(context).pop(currentSelects);
    });
  }

  void onCancel() {
    currentSelects.clear();
    update();
  }
}
